package com.x2.modular.pack.kit;

import com.x2.modular.pack.config.XyPackConfModule;
import com.x2.modular.pack.config.XyPackConfProject;

import java.io.File;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
 * 打包
 */
public class PackKit {

    /**
     * 指定整个工程
     *
     * @param project
     * @throws Exception
     */
    public static void actionProject(XyPackConfProject project) throws Exception {
        long start;
        System.out.println("*******打包开始");
        for (XyPackConfModule module : project.getModuleList()) {
            start = System.currentTimeMillis();
            System.out.println("*******" + module.getCodeFile() + "打包开始");
            actionModule(project, module);
            System.out.println("*******" + module.getCodeFile() + "打包完成，耗时：" + (System.currentTimeMillis() - start));
        }
        System.out.println("*******打包完成，输出地址：" + project.getOutBaseDir());

    }

    /**
     * 执行各个模块
     *
     * @param project
     * @param module
     * @throws Exception
     */
    private static void actionModule(XyPackConfProject project, XyPackConfModule module) throws Exception {
        if (module == null) {
            throw new Exception("模块不存在！");
        }
        if (module.getCodeFile() == null) {
            throw new Exception("代码不存在！");
        }
        File codeFile = new File(project.getCodeBaseDir() + "/" + module.getCodeFile());
        if (!codeFile.exists()) {
            throw new Exception(codeFile.getAbsolutePath() + "代码不存在！");
        }
        File dir = new File(project.getOutBaseDir() + "/" + module.getOutDir());
        if (dir.exists()) {
            if (!dir.delete()) {
                throw new Exception(dir.getAbsolutePath() + "导出位置，已经存在且不能删除！");
            }
        }
        //创建目录
        dir.mkdirs();
        //解压缩
        String basePath = dir.getAbsolutePath();
        WarKit.unzipWar(codeFile.getAbsolutePath(), basePath);
        //删除配置文件
        deleteConfigBySuffix(new File(basePath + "/WEB-INF/classes"), ".yml", ".xml", ".json", ".ico", ".lic");
        //删除无用文件
        deleteExcludeByPrefix(new File(basePath + "/META-INF"), null);
        //删除无用文件
        deleteExcludeByPrefix(new File(basePath + "/favicon.ico"), null);
        //删除无用jar
        List<String> excludePrefixFileNames = new ArrayList<>();
        excludePrefixFileNames.add("lib");
        if (project.getPrefixJarName() != null && project.getPrefixJarName().length() > 0) {
            excludePrefixFileNames.addAll(Arrays.asList(project.getPrefixJarName().split(",")));
        }
        deleteExcludeByPrefix(new File(basePath + "/WEB-INF/lib"), excludePrefixFileNames);

    }

    /**
     * 删除文件，保留指定名称开头的文件
     *
     * @param file
     * @param excludePrefixFileNames
     */
    private static void deleteExcludeByPrefix(File file, List<String> excludePrefixFileNames) {
        if (file.isDirectory()) {
            for (File subFile : file.listFiles()) {
                deleteExcludeByPrefix(subFile, excludePrefixFileNames);

            }
            int size = file.listFiles().length;
            if (size == 0) {
                file.delete();
            }
        } else {
            if (excludePrefixFileNames == null || excludePrefixFileNames.size() < 0) {
                file.delete();
            }
            for (String name : excludePrefixFileNames) {
                if (file.getName().startsWith(name.trim())) {
                    return;
                }
            }
            file.delete();
        }


    }

    /**
     * 删除指定目录下，以特定文字结尾的文件
     *
     * @param file
     * @param retainFileNames
     */
    private static void deleteConfigBySuffix(File file, String... retainFileNames) {
        for (File subFile : file.listFiles()) {
            if (!subFile.isFile()) {
                continue;
            }
            for (String name : retainFileNames) {
                if (subFile.getName().endsWith(name)) {
                    subFile.delete();
                }
            }
        }
    }
}
